package com.xcy.quickhand.spider;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.http.HttpRequest;
import cn.hutool.json.JSONUtil;
import com.xcy.quickhand.model.A;
import com.xcy.quickhand.model.AuthorInfo;
import com.xcy.quickhand.model.FollowerResponse;
import com.xcy.quickhand.model.Video;

import java.util.*;

/**
 * @author xcy
 * @version V1.0
 * @description 爬取视频工具类
 * @date 2023/2/11 21:29
 */
public class CrawlVideoUtils {

    // 爬取作者的所有视频
    public static List<Video> crawlVideoListByAuthorId(String cookie, String userId) {
        List<Video> pageList = crawlPageVideo("", cookie, userId, 1);
        return pageList;
    }


    private static List<Video> crawlPageVideo(String cursor, String cookie, String userId, Integer page) {
        String url = "https://www.kuaishou.com/graphql";

        System.out.println("正在爬取的页码: " + page);

        // 所有的视频作品
        List videoList = new ArrayList<Video>();

        String response = HttpRequest.post(url).header("cookie", cookie)
                .header("content-type", "application/json")
                .header("Host", "www.kuaishou.com")
                .header("Origin", "https://www.kuaishou.com")
                .header("Referer", "https://www.kuaishou.com/profile/3xgz9zaku7hig96")
                .header("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36")
                .body(
                        "{\n" +
                                "    \"operationName\": \"visionProfilePhotoList\",\n" +
                                "    \"variables\": {\n" +
                                "        \"userId\": \"" + userId + "\",\n" +
                                "        \"pcursor\": \"" + cursor + "\",\n" +
                                "        \"page\": \"profile\"\n" +
                                "    },\n" +
                                "    \"query\": \"fragment photoContent on PhotoEntity {\\n  id\\n  duration\\n  caption\\n  originCaption\\n  likeCount\\n  viewCount\\n  realLikeCount\\n  coverUrl\\n  photoUrl\\n  photoH265Url\\n  manifest\\n  manifestH265\\n  videoResource\\n  coverUrls {\\n    url\\n    __typename\\n  }\\n  timestamp\\n  expTag\\n  animatedCoverUrl\\n  distance\\n  videoRatio\\n  liked\\n  stereoType\\n  profileUserTopPhoto\\n  musicBlocked\\n  __typename\\n}\\n\\nfragment feedContent on Feed {\\n  type\\n  author {\\n    id\\n    name\\n    headerUrl\\n    following\\n    headerUrls {\\n      url\\n      __typename\\n    }\\n    __typename\\n  }\\n  photo {\\n    ...photoContent\\n    __typename\\n  }\\n  canAddComment\\n  llsid\\n  status\\n  currentPcursor\\n  tags {\\n    type\\n    name\\n    __typename\\n  }\\n  __typename\\n}\\n\\nquery visionProfilePhotoList($pcursor: String, $userId: String, $page: String, $webPageArea: String) {\\n  visionProfilePhotoList(pcursor: $pcursor, userId: $userId, page: $page, webPageArea: $webPageArea) {\\n    result\\n    llsid\\n    webPageArea\\n    feeds {\\n      ...feedContent\\n      __typename\\n    }\\n    hostName\\n    pcursor\\n    __typename\\n  }\\n}\\n\"\n" +
                                "}"
                ).execute().body();


        A a = JSONUtil.toBean(response, A.class);

        if(null == a.getData()){
            return null;
        }
        // 下一页游标
        String nextCursor = a.getData().getVisionProfilePhotoList().getPcursor();

        List<A.DataDTO.VisionProfilePhotoListDTO.FeedsDTO> feeds = a.getData().getVisionProfilePhotoList().getFeeds();


        for (int i = 0; i < feeds.size(); i++) {
            A.DataDTO.VisionProfilePhotoListDTO.FeedsDTO feedsDTO = feeds.get(i);
            A.DataDTO.VisionProfilePhotoListDTO.FeedsDTO.AuthorDTO author = feedsDTO.getAuthor();

            // 作者id
            String authorId = author.getId();
            System.out.println("作者id " + authorId);
            // 作者头像
            String headerUrl = author.getHeaderUrl();
            System.out.println("作者头像 " + headerUrl);
            // 作者名称
            String authorName = author.getName();
            System.out.println("作者名称 " + authorName);

            A.DataDTO.VisionProfilePhotoListDTO.FeedsDTO.PhotoDTO photo = feedsDTO.getPhoto();

            // 视频唯一id(待确认是否是全局唯一)
            String videoId = photo.getId();
            System.out.println("视频唯一id " + videoId);
            // 动态缩略图
            String animatedCoverUrl = photo.getAnimatedCoverUrl();
            System.out.println("动态缩略图 " + animatedCoverUrl);
            // 封面图
            String coverUrl = photo.getCoverUrl();
            System.out.println("封面图 " + coverUrl);
            // 标题
            String caption = photo.getCaption();

            System.out.println("标题 " + caption);
            // 视频地址高清
            String photoUrl = photo.getPhotoUrl();
            System.out.println("视频地址高清 " + photoUrl);

            // 视频地址低清
            String photoH265Url = photo.getPhotoH265Url();
            System.out.println("视频地址低清 " + photoH265Url);

            Video video = new Video();
            video.setVideoId(videoId);
            video.setAnimatedOverUrl(animatedCoverUrl);
            video.setCoverUrl(coverUrl);
            video.setVideoCaption(caption);
            video.setPhotoUrl(photoUrl);
            video.setPhotoH265Url(photoH265Url);
            video.setAuthorId(authorId);
            video.setHeaderUrl(headerUrl);
            video.setAuthorName(authorName);
            video.setCreateTime(new Date());

            videoList.add(video);
        }

        if (!nextCursor.equals("no_more")) {
            page = page + 1;
            List<Video> videos = crawlPageVideo(nextCursor, cookie, userId, page);
            if (CollectionUtil.isNotEmpty(videos)) {
                videoList.addAll(videos);
            }
        }

        return videoList;
    }


    public static List<AuthorInfo> crawlAuthor(String cookie) {
        return crawlAuthor("", cookie, 1);
    }

    /**
     * 爬取作者
     * @param cursor
     * @param cookie
     * @param page
     * @return
     */
    public static List<AuthorInfo> crawlAuthor(String cursor, String cookie, Integer page) {
        String url = "https://www.kuaishou.com/graphql";

        System.out.println("正在爬取的页码: " + page);

        // 所有的关注用户
        List authorInfoList = new ArrayList<AuthorInfo>();

        String response = HttpRequest.post(url).header("cookie", cookie)
                .header("content-type", "application/json")
                .header("Host", "www.kuaishou.com")
                .header("Origin", "https://www.kuaishou.com")
                .header("Referer", "https://www.kuaishou.com/profile/3xgz9zaku7hig96")
                .header("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36")
                .body(
                        //"{\n" +
                        //        "    \"operationName\": \"visionProfilePhotoList\",\n" +
                        //        "    \"variables\": {\n" +
                        //        "        \"userId\": \"" + userId + "\",\n" +
                        //        "        \"pcursor\": \"" + cursor + "\",\n" +
                        //        "        \"page\": \"profile\"\n" +
                        //        "    },\n" +
                        //        "    \"query\": \"fragment photoContent on PhotoEntity {\\n  id\\n  duration\\n  caption\\n  originCaption\\n  likeCount\\n  viewCount\\n  realLikeCount\\n  coverUrl\\n  photoUrl\\n  photoH265Url\\n  manifest\\n  manifestH265\\n  videoResource\\n  coverUrls {\\n    url\\n    __typename\\n  }\\n  timestamp\\n  expTag\\n  animatedCoverUrl\\n  distance\\n  videoRatio\\n  liked\\n  stereoType\\n  profileUserTopPhoto\\n  musicBlocked\\n  __typename\\n}\\n\\nfragment feedContent on Feed {\\n  type\\n  author {\\n    id\\n    name\\n    headerUrl\\n    following\\n    headerUrls {\\n      url\\n      __typename\\n    }\\n    __typename\\n  }\\n  photo {\\n    ...photoContent\\n    __typename\\n  }\\n  canAddComment\\n  llsid\\n  status\\n  currentPcursor\\n  tags {\\n    type\\n    name\\n    __typename\\n  }\\n  __typename\\n}\\n\\nquery visionProfilePhotoList($pcursor: String, $userId: String, $page: String, $webPageArea: String) {\\n  visionProfilePhotoList(pcursor: $pcursor, userId: $userId, page: $page, webPageArea: $webPageArea) {\\n    result\\n    llsid\\n    webPageArea\\n    feeds {\\n      ...feedContent\\n      __typename\\n    }\\n    hostName\\n    pcursor\\n    __typename\\n  }\\n}\\n\"\n" +
                        //        "}"

                        "{\n" +
                                "    \"operationName\": \"visionProfileUserList\",\n" +
                                "    \"variables\": {\n" +
                                "        \"ftype\": 1\n" +
                                "    },\n" +
                                "    \"query\": \"query visionProfileUserList($pcursor: String, $ftype: Int) {\\n  visionProfileUserList(pcursor: $pcursor, ftype: $ftype) {\\n    result\\n    fols {\\n      user_name\\n      headurl\\n      user_text\\n      isFollowing\\n      user_id\\n      __typename\\n    }\\n    hostName\\n    pcursor\\n    __typename\\n  }\\n}\\n\"\n" +
                                "}"
                ).execute().body();


        FollowerResponse a = JSONUtil.toBean(response, FollowerResponse.class);

        if(null == a.getData()){
            return null;
        }
        // 下一页游标
        String nextCursor = a.getData().getVisionProfileUserList().getPcursor();

        List<FollowerResponse.DataDTO.VisionProfileUserListDTO.FolsDTO> fols = a.getData().getVisionProfileUserList().getFols();


        for (int i = 0; i < fols.size(); i++) {
            FollowerResponse.DataDTO.VisionProfileUserListDTO.FolsDTO folsDTO = fols.get(i);
            // 作者头像
            String headurl = folsDTO.getHeadurl();
            System.out.println("作者头像 " + headurl);
            // 作者id
            String userId = folsDTO.getUserId();
            System.out.println("作者id " + userId);
            // 作者名称
            String userName = folsDTO.getUserName();
            System.out.println("作者名称 " + userName);

            AuthorInfo authorInfo = new AuthorInfo();
            authorInfo.setAuthorId(userId);
            authorInfo.setHeaderUrl(headurl);
            authorInfo.setAuthorName(userName);
            authorInfo.setCreateTime(new Date());

            authorInfoList.add(authorInfo);
        }

        if (!nextCursor.equals("no_more")) {
            page = page + 1;
            List<AuthorInfo> authorInfos = crawlAuthor(nextCursor, cookie, page);
            if (CollectionUtil.isNotEmpty(authorInfos)) {
                authorInfoList.addAll(authorInfos);
            }
        }

        return authorInfoList;
    }
}
